import React from 'react'
import { Link } from 'react-router-dom'

// 引入封装好的导航组件
import NavHeader from '../../components/NavHeader'
import { Toast } from 'antd-mobile'


// 导入样式
// import './index.scss'
import styles from './index.module.css'

import { BASE_URL } from '../../utils/url'
import { API } from '../../utils/api'
import HouseItem from '../../components/HouseItem'

const BMap = window.BMapGL
const labelStyle = {
  cursor: 'pointer',
  border: '0px solid rgb(255,0,0)',
  padding: '0px',
  whiteSpace: 'nowrap',
  fontSize: '12px',
  color: 'rgb(255,255,255)',
  textAlign: 'center'
}

export default class Map extends React.Component {
  state = {
    // 小区下的房源列表
    houseList: [],
    isShowList: false
  }

  componentDidMount() {
    this.setMapInfo()
  }

  // 初始化地图信息
  setMapInfo() {
    const { label, value } = JSON.parse(localStorage.getItem('hkzf_city'))

    // 用window全局获取需要的Map相关
    const map = new BMap.Map('container')

    // 能在其他方法中通过this获取map对象
    this.map = map

    // 设置中心点坐标
    // const point = new window.BMapGL.Point(116.404, 39.915)
    // 创建地址解析器实例     
    const myGeo = new BMap.Geocoder();

    // 将地址解析结果显示在地图上，并调整地图视野    
    myGeo.getPoint(label, async point => {
      if (point) {
        // 初始化地图 
        map.centerAndZoom(point, 11);
        // 添加功能控件
        map.addControl(new BMap.ScaleControl());  // 比例尺
        map.addControl(new BMap.NavigationControl());   // 平移缩放

        this.renderOverlays(value)
      }
    }, label);

    // 给地图绘制移动事件
    map.addEventListener('movestart', () => {
      // console.log('移动了')
      if (this.state.isShowList) {
        this.setState({
          isShowList: false
        })
      }
    })
  }

  // 渲染覆盖物入口
  async renderOverlays(id) {
    try {
      // 开启loading
      Toast.loading('加载中...', 0, null, false)

      // 根据区域ID，获取区域内租房信息
      const res = await (await API.get(`/area/map?id=${id}`)).data.body

      // 关闭loading
      Toast.hide()

      // 调用方法获取类型和缩放级别
      const { nextZoom, type } = this.getTypeAndZoom()
      res.forEach(item => {
        this.createOverlays(item, nextZoom, type)
      });
    } catch (e) {
      // 关闭loading
      Toast.hide()
    }
  }

  // 计算覆盖物类型和下一个缩放级别
  getTypeAndZoom() {
    // 调用地图getZoom() 来获取当前缩放级别
    const zoom = this.map.getZoom()
    // console.log('现在的级别是', zoom)
    let nextZoom, type   //分别表示下一个缩放级别  和 覆盖物类型
    if (zoom >= 10 && zoom < 12) {
      // 区
      nextZoom = 13
      type = 'circle'
    } else if (zoom >= 12 && zoom < 14) {
      // 镇
      nextZoom = 15
      type = 'circle'
    } else if (zoom >= 14 && zoom < 16) {
      // 小区
      type = 'rect'
    }
    return {
      nextZoom, type
    }
  }

  // 创建覆盖物
  async createOverlays(data, zoom, type) {
    const { label: areaName, coord: { latitude, longitude }, count, value } = data
    const areaPoint = new BMap.Point(longitude, latitude)
    if (type === 'circle') {
      // 区或镇
      this.createCircle(areaPoint, areaName, count, value, zoom)
    } else {
      // 小区
      this.createRect(areaPoint, areaName, count, value)
    }
  }

  // 创建区或镇覆盖物
  createCircle(point, name, count, id, zoom) {
    const opts = {
      position: point,
      offset: new BMap.Size(-35, -35)
    }
    const label = new BMap.Label('', opts)

    // 给label对象设置唯一标识
    label.id = id

    // 设置房源覆盖物内容
    label.setContent(`
    <div class="${styles.bubble}">
      <p class="${styles.name}">${name}</p>
      <p>${count}套</p>
    </div>
    `)
    // 设置样式
    label.setStyle(labelStyle)

    // 添加文本点击事件
    label.addEventListener('click', () => {
      // 调用renderOverlays,获取该区域下的房源数据
      this.renderOverlays(id)

      // 以当前点击的目标为中心放大地图
      this.map.centerAndZoom(point, zoom);
      // 清除当前覆盖物信息
      this.map.clearOverlays()
    })

    // 添加遮盖
    this.map.addOverlay(label)
  }

  // 创建小区覆盖物
  createRect(point, name, count, id) {
    const opts = {
      position: point,
      offset: new BMap.Size(-50, -28)
    }
    const label = new BMap.Label('', opts)

    // 给label对象设置唯一标识
    label.id = id

    // 设置房源覆盖物内容
    label.setContent(`
    <div class="${styles.rect}">
      <span class="${styles.houseName}">${name}</span>
      <span class="${styles.houseNum}">${count}套</span>
      <i class="${styles.arrow}"></i>
    </div>
    `)

    // 设置样式
    label.setStyle(labelStyle)

    // 添加文本点击事件
    label.addEventListener('click', (e) => {
      // console.log('被点击了')
      this.getHouseList(id)

      // 获取当前被点击项
      const target = e.domEvent.changedTouches[0]
      // 点击后将地图移动到中心位置
      this.map.panBy(
        window.innerWidth / 2 - target.clientX,
        (window.innerHeight - 330) / 2 - target.clientY
      )
    })
    // 添加遮盖
    this.map.addOverlay(label)
  }

  // 根据id获取获取小区房源信息
  async getHouseList(id) {
    try {
      // 开启loading
      Toast.loading('加载中...', 0, null, false)
      const res = await (await API.get(`/houses?cityId=${id}`)).data.body
      // console.log(res)
      Toast.hide()

      this.setState({
        houseList: res.list,

        // 展示房源列表
        isShowList: true
      })
    } catch (e) {
      // 关闭加载
      Toast.hide()
    }
  }

  // 封装渲染房屋列表的方法
  renderHouseList() {
    return (
      <div className={[styles.houseList, this.state.isShowList ? styles.show : ''].join(' ')}>
        <div className={styles.titleWrap}>
          <h1 className={styles.listTitle}>房屋列表</h1>
          <Link className={styles.titleMore} to="/home/list">更多房源</Link>
        </div>

        <div className={styles.houseItems}>
          {/* 房屋结构 */}
          {this.state.houseList.map(item =>
            <HouseItem
              key={item.houseCode}
              src={BASE_URL + item.houseImg}
              title={item.title}
              desc={item.desc}
              tags={item.tags}
              price={item.price}
            />
          )}
        </div>
      </div>
    )
  }

  render() {
    return (
      <div className={styles.map}>
        {/* 顶部导航栏 */}
        <NavHeader name="地图信息" onLeftClick={() => {
          console.log('点击了左侧按钮')
        }} />
        <div id="container" className={styles.container}>1111111111</div>

        {/* 房源列表 */}
        {this.renderHouseList()}
      </div>)
  }
}